#include "config_infoset.h"
#include "ui_config_infoset.h"

config_infoSet::config_infoSet(QWidget *parent, QString name)
    : QWidget(parent), ui(new Ui::config_infoSet)
{
    ui->setupUi(this);
    ui->label_name->setText(name);
    initUi();
    setAttribute(Qt::WA_StyledBackground); // 这句不加,样式表是加载不出来的
}

config_infoSet::~config_infoSet()
{
    delete ui;
}
/**
 * @brief config_infoSet::initUi 初始化一些ui
 */
void config_infoSet::initUi()
{
    // 无边框设置

    ui->tableWidget->setFrameShape(QFrame::NoFrame);

    // 列宽自适应
    ui->tableWidget->horizontalHeader()->setSectionResizeMode(QHeaderView::Stretch);
    ui->tableWidget->verticalHeader()->setSectionResizeMode(QHeaderView::ResizeToContents);

    // 触摸滚动支持
    QScroller::grabGesture(ui->tableWidget->viewport(), QScroller::TouchGesture); // 允许触摸滑动
    ui->tableWidget->setVerticalScrollMode(QAbstractItemView::ScrollPerPixel);

    // 基础设置
    ui->tableWidget->setColumnCount(3); // 按需设置列数
    ui->tableWidget->setHorizontalHeaderLabels({"位置", "地址", "数据类型"});
    // 设置整行选中模式
    ui->tableWidget->setSelectionBehavior(QAbstractItemView::SelectRows);
    // 初始化所有可选位置
    allLocations << "母线A" << "母线B" << "母线C"
                 << "上触头A" << "上触头B" << "上触头C"
                 << "下触头A" << "下触头B" << "下触头C"
                 << "电缆A" << "电缆B" << "电缆C"
                 << "柜内温度" << "柜内湿度"
                 << "超声波" << "暂态地电压";
}

void config_infoSet::setOperateEnable(bool enabled)
{
    ui->info_add->setEnabled(enabled);
    ui->info_change->setEnabled(enabled);
    ui->info_delete->setEnabled(enabled);
}

/**
 * @brief config_infoSet::sortConfigInfoByLocations 按allLocations顺序对配置信息进行排序
 * @param params 要排序的配置信息
 * @return 排序后的配置信息列表
 */
QList<ConfigInfo> config_infoSet::sortConfigInfoByLocations(const QMap<QString, ConfigInfo> &params)
{
    QList<ConfigInfo> sortedParams;

    // 首先按allLocations顺序添加参数
    for (const QString &location : allLocations)
    {
        // 查找params中是否有这个位置
        for (auto it = params.begin(); it != params.end(); ++it)
        {
            if (it.value().position == location)
            {
                sortedParams.append(it.value());
                break;
            }
        }
    }

    // 然后添加不在allLocations中的参数（如果有的话）
    for (auto it = params.begin(); it != params.end(); ++it)
    {
        if (!allLocations.contains(it.value().position))
        {
            sortedParams.append(it.value());
        }
    }

    return sortedParams;
}

/**
 * @brief config_infoSet::findInsertPosition 查找新项应该插入的位置
 * @param selectedLocation 选中的位置
 * @return 应该插入的行索引
 */
int config_infoSet::findInsertPosition(const QString &selectedLocation)
{
    int insertRow = ui->tableWidget->rowCount(); // 默认插入到最后

    // 查找选中位置在allLocations中的索引
    int selectedIndex = allLocations.indexOf(selectedLocation);
    if (selectedIndex == -1)
    {
        // 如果位置不在allLocations中，插入到最后
        return ui->tableWidget->rowCount();
    }

    // 查找正确的插入位置
    insertRow = 0; // 默认从第一个位置开始查找

    // 遍历所有行，找到第一个位置索引大于等于选中索引的行
    for (int row = 0; row < ui->tableWidget->rowCount(); ++row)
    {
        QTableWidgetItem *item = ui->tableWidget->item(row, 0);
        if (item)
        {
            int existingIndex = allLocations.indexOf(item->text());
            if (existingIndex == -1)
            {
                // 如果现有位置不在allLocations中，继续查找
                continue;
            }
            // 如果当前行的位置索引大于等于选中位置的索引，则在此处插入
            if (existingIndex >= selectedIndex)
            {
                insertRow = row;
                break;
            }
        }
    }

    // 如果遍历完所有行都没有找到合适的位置，插入到最后
    if (insertRow == 0 && ui->tableWidget->rowCount() > 0)
    {
        QTableWidgetItem *lastItem = ui->tableWidget->item(ui->tableWidget->rowCount() - 1, 0);
        if (lastItem)
        {
            int lastIndex = allLocations.indexOf(lastItem->text());
            if (lastIndex < selectedIndex)
            {
                insertRow = ui->tableWidget->rowCount();
            }
        }
    }

    return insertRow;
}

/**
 * @brief config_infoSet::setParameters 根据内容更新参数ui，按allLocations顺序插入
 * @param params
 */
void config_infoSet::setParameters(QMap<QString, ConfigInfo> params)
{
    // 清空现有内容
    ui->tableWidget->clearContents();
    ui->tableWidget->setRowCount(0);

    // 使用独立的排序函数对参数进行排序
    QList<ConfigInfo> sortedParams = sortConfigInfoByLocations(params);

    // 按排序后的顺序插入数据
    for (const ConfigInfo &info : sortedParams)
    {
        // 插入新行
        int row = ui->tableWidget->rowCount();
        ui->tableWidget->insertRow(row);

        // 填充数据
        ui->tableWidget->setItem(row, 0, new QTableWidgetItem(info.position));
        ui->tableWidget->setItem(row, 1, new QTableWidgetItem(QString::number(info.id)));
        ui->tableWidget->setItem(row, 2, new QTableWidgetItem(info.dataType));
    }
}
/**
 * @brief config_infoSet::getConfigInfo 返回当前页面的tableWidget内容
 * @return
 */
QMap<QString, ConfigInfo> config_infoSet::getConfigInfo()
{
    QMap<QString, ConfigInfo> configMap;

    for (int row = 0; row < ui->tableWidget->rowCount(); ++row)
    {
        // 提取三列数据
        QTableWidgetItem *itemPos = ui->tableWidget->item(row, 0);
        QTableWidgetItem *itemID = ui->tableWidget->item(row, 1);
        QTableWidgetItem *itemType = ui->tableWidget->item(row, 2);

        if (itemPos && itemID && itemType)
        {
            ConfigInfo info;
            info.position = itemPos->text();
            info.id = itemID->text().toInt();
            info.dataType = itemType->text();
            info.data = "--";
            // 以位置作为key（根据setParameters逻辑）
            configMap.insert(QString::number(row, 10), info);
        }
    }
    return configMap;
}

/**
 * @brief config_infoSet::on_info_add_clicked 新增一个监测点
 */
void config_infoSet::on_info_add_clicked()
{
    // 创建输入对话框
    QDialog dialog(this);
    dialog.setWindowTitle("新增监测点");
    // dialog.resize(300, 200);
    QFormLayout form(&dialog);

    // 获取当前已使用的选项
    QStringList usedLocations;
    for (int row = 0; row < ui->tableWidget->rowCount(); ++row)
    {
        QTableWidgetItem *item = ui->tableWidget->item(row, 0);
        if (item)
        {
            usedLocations.append(item->text());
        }
    }

    // 计算可用选项
    QStringList availableLocations;
    for (const QString &location : allLocations)
    {
        if (!usedLocations.contains(location))
        {
            availableLocations.append(location);
        }
    }

    // 位置选择下拉框
    QComboBox cbLocation;
    cbLocation.setEditable(true);
    cbLocation.addItems(availableLocations);
    cbLocation.setCurrentIndex(-1);
    cbLocation.setPlaceholderText("选择或输入位置");
    cbLocation.setMinimumHeight(30);
    cbLocation.setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::Fixed);
    form.addRow("位置：", &cbLocation);

    // Modbus地址输入
    CustomLineEdit leAddress;
    leAddress.setValidator(new QIntValidator(0, 65535, this));
    leAddress.setMinimumHeight(30);
    form.addRow("地址：", &leAddress);

    // 数据类型显示标签（只读）
    QLabel dataTypeLabel;
    dataTypeLabel.setText("温度");
    dataTypeLabel.setMinimumHeight(30);
    form.addRow("数据类型：", &dataTypeLabel);

    // 添加位置选择变化时自动设置数据类型的逻辑
    QObject::connect(&cbLocation, &QComboBox::currentTextChanged, [&dataTypeLabel](const QString &text)
                     {
        if (text == "柜内湿度") {
            dataTypeLabel.setText("柜内湿度");
        }
        else if (text == "柜内温度")
        {
            dataTypeLabel.setText("柜内温度");
        }
        else if (text == "超声波")
        {
            dataTypeLabel.setText("超声波");
        }
        else if (text == "暂态地电压")
        {
            dataTypeLabel.setText("暂态地电压");
        }
        else if (!text.isEmpty())
        {
            dataTypeLabel.setText("温度");
        } });

    // 确认按钮
    QDialogButtonBox btnBox(QDialogButtonBox::Ok | QDialogButtonBox::Cancel);
    form.addRow(&btnBox);
    QObject::connect(&btnBox, &QDialogButtonBox::accepted, &dialog, &QDialog::accept);
    QObject::connect(&btnBox, &QDialogButtonBox::rejected, &dialog, &QDialog::reject);
    dialog.setWindowModality(Qt::WindowModal);
    btnBox.button(QDialogButtonBox::Ok)->setText("是");
    btnBox.button(QDialogButtonBox::Cancel)->setText("否");
    if (dialog.exec() == QDialog::Accepted)
    {
        // 输入验证
        if (cbLocation.currentText().trimmed().isEmpty() || leAddress.text().isEmpty())
        {
            QMessageBox msgBox(this);
            msgBox.setWindowTitle("输入错误");
            msgBox.setText("请填写完整信息");
            msgBox.setStandardButtons(QMessageBox::Ok);
            msgBox.setButtonText(QMessageBox::Ok, "确定");
            msgBox.exec();
            return;
        }

        // 检查地址是否重复
        QString newAddress = leAddress.text();
        for (int row = 0; row < ui->tableWidget->rowCount(); ++row)
        {
            QTableWidgetItem *item = ui->tableWidget->item(row, 1);
            if (item && item->text() == newAddress)
            {
                QMessageBox msgBox(this);
                msgBox.setWindowTitle("地址重复");
                msgBox.setText("该地址已存在，请重新输入");
                msgBox.setStandardButtons(QMessageBox::Ok);
                msgBox.setButtonText(QMessageBox::Ok, "确定");
                msgBox.exec();
                return;
            }
        }

        // 确定插入位置（按allLocations顺序）
        QString selectedLocation = cbLocation.currentText();

        // 使用独立的函数查找插入位置
        int insertRow = findInsertPosition(selectedLocation);

        // 插入新行到正确位置
        ui->tableWidget->insertRow(insertRow);

        // 设置表格项
        ui->tableWidget->setItem(insertRow, 0, new QTableWidgetItem(selectedLocation));
        ui->tableWidget->setItem(insertRow, 1, new QTableWidgetItem(leAddress.text()));

        // 根据位置自动设置数据类型
        QString dataType;
        if (selectedLocation == "柜内湿度")
        {
            dataType = "柜内湿度";
        }
        else if (selectedLocation == "柜内温度")
        {
            dataType = "柜内温度";
        }
        else if (selectedLocation == "超声波")
        {
            dataType = "超声波";
        }
        else if (selectedLocation == "暂态地电压")
        {
            dataType = "暂态地电压";
        }
        else
        {
            dataType = "温度"; // 默认为温度类型
        }
        // QString dataType = (selectedLocation == "柜内湿度") ? "湿度" : "温度";
        ui->tableWidget->setItem(insertRow, 2, new QTableWidgetItem(dataType));
    }
}
/**
 * @brief config_infoSet::on_info_change_clicked 打开选中行，修改内容和确定可以更新那一行内容
 */
void config_infoSet::on_info_change_clicked()
{
    // 获取当前选中行
    int row = ui->tableWidget->currentRow();
    if (row == -1)
    {
        QMessageBox::warning(this, "提示", "请先选择要修改的行");
        return;
    }

    // 创建编辑对话框
    QDialog dialog(this);
    dialog.setWindowTitle("修改监测点");
    QFormLayout form(&dialog);

    // 显示当前位置（只读）
    QLabel locationLabel;
    QString currentLocation = ui->tableWidget->item(row, 0)->text();
    locationLabel.setText(currentLocation);
    locationLabel.setMinimumHeight(30);
    form.addRow("安装位置：", &locationLabel);

    // Modbus地址输入
    CustomLineEdit leAddress;
    leAddress.setValidator(new QIntValidator(0, 65535, this));
    leAddress.setText(ui->tableWidget->item(row, 1)->text());
    leAddress.setMinimumHeight(30);
    form.addRow("地址：", &leAddress);

    // 数据类型显示标签（只读）
    QLabel dataTypeLabel;
    QString currentDataType;
    if (currentLocation == "柜内湿度")
    {
        currentDataType = "柜内湿度";
    }
    else if (currentLocation == "柜内温度")
    {
        currentDataType = "柜内温度";
    }
    else if (currentLocation == "超声波")
    {
        currentDataType = "超声波";
    }
    else if (currentLocation == "暂态地电压")
    {
        currentDataType = "暂态地电压";
    }
    else
    {
        currentDataType = "温度";
    }
    // QString currentDataType = (currentLocation == "柜内湿度") ? "湿度" : "温度";
    dataTypeLabel.setText(currentDataType);
    dataTypeLabel.setMinimumHeight(30);
    form.addRow("数据类型：", &dataTypeLabel);

    // 确认按钮
    QDialogButtonBox btnBox(QDialogButtonBox::Ok | QDialogButtonBox::Cancel);
    form.addRow(&btnBox);
    QObject::connect(&btnBox, &QDialogButtonBox::accepted, &dialog, &QDialog::accept);
    QObject::connect(&btnBox, &QDialogButtonBox::rejected, &dialog, &QDialog::reject);
    dialog.setWindowModality(Qt::WindowModal);
    btnBox.button(QDialogButtonBox::Ok)->setText("是");
    btnBox.button(QDialogButtonBox::Cancel)->setText("否");
    if (dialog.exec() == QDialog::Accepted)
    {
        // 输入验证
        if (leAddress.text().isEmpty())
        {
            QMessageBox msgBox(this);
            msgBox.setWindowTitle("输入错误");
            msgBox.setText("地址不能为空");
            msgBox.setStandardButtons(QMessageBox::Ok);
            msgBox.setButtonText(QMessageBox::Ok, "确定");
            msgBox.exec();
            return;
        }

        // 检查地址是否重复（排除当前行）
        QString newAddress = leAddress.text();
        QString currentAddress = ui->tableWidget->item(row, 1)->text();

        // 只有当地址发生改变时才检查重复
        if (newAddress != currentAddress)
        {
            for (int i = 0; i < ui->tableWidget->rowCount(); ++i)
            {
                if (i != row)
                { // 排除当前行
                    QTableWidgetItem *item = ui->tableWidget->item(i, 1);
                    if (item && item->text() == newAddress)
                    {
                        QMessageBox msgBox(this);
                        msgBox.setWindowTitle("地址重复");
                        msgBox.setText("该地址已存在，请重新输入");
                        msgBox.setStandardButtons(QMessageBox::Ok);
                        msgBox.setButtonText(QMessageBox::Ok, "确定");
                        msgBox.exec();
                        return;
                    }
                }
            }
        }

        // 更新表格数据（只更新地址）
        ui->tableWidget->item(row, 1)->setText(newAddress);
    }
}
/**
 * @brief config_infoSet::on_info_delete_clicked 删除对应行
 */
void config_infoSet::on_info_delete_clicked()
{
    int row = ui->tableWidget->currentRow();
    if (row == -1)
    {
        QMessageBox msgBox(this);
        msgBox.setWindowTitle("提示");
        msgBox.setText("请先选择要删除的行");
        msgBox.setStandardButtons(QMessageBox::Ok);
        msgBox.setButtonText(QMessageBox::Ok, "确定");
        msgBox.exec();
        return;
    }

    QMessageBox msgBox(this);
    msgBox.setWindowTitle("确认");
    msgBox.setText("确定删除该行吗？");
    msgBox.setStandardButtons(QMessageBox::Yes | QMessageBox::No);
    msgBox.setButtonText(QMessageBox::Yes, "是");
    msgBox.setButtonText(QMessageBox::No, "否");
    if (msgBox.exec() == QMessageBox::Yes)
    {
        ui->tableWidget->removeRow(row);
    }
}
void config_infoSet::setBlockName(QString name)
{
    ui->label_name->setText(name);
}